package raz.examples.thread;

//http://docs.oracle.com/javase/tutorial/essential/concurrency/simple.html

/**
 * The following example brings together some of the concepts of this section.
 * SimpleThreads consists of two threads. The first is the main thread that
 * every Java application has. The main thread creates a new thread from the
 * Runnable object, MessageLoop, and waits for it to finish. If the MessageLoop
 * thread takes too long to finish, the main thread interrupts it.
 * 
 * The MessageLoop thread prints out a series of messages. If interrupted before
 * it has printed all its messages, the MessageLoop thread prints a message and
 * exits.
 * */

public class SimpleThreads {

	/**
	 * Display a message, preceded by the name of the current thread
	 */
	static void threadMessage(String message) {
		String threadName = Thread.currentThread().getName();
		System.out.format("%s: %s%n", threadName, message);
	}

	private static class MessageLoop implements Runnable {

		String importantInfo[] = { "Mares eat oats", "Does eat oats",
				"Little lambs eat ivy", "A kid will eat ivy too" };

		@Override
		public void run() {
			try {
				for (int i = 0; i < importantInfo.length; i++) {
					// Pause for 4 seconds
					Thread.sleep(4000);
					// Print a message
					threadMessage(importantInfo[i]);
				}
			} catch (InterruptedException e) {
				threadMessage("I wasn't done!");
			}

		}
	}

	public static void main(String[] args) throws InterruptedException {

		/**
		 * Delay, in milliseconds before we interrupt MessageLoop thread
		 * (default one hour).
		 */
		long patience = 1000 * 60 * 60;

		threadMessage("Starting MessageLoop thread");
		long startTime = System.currentTimeMillis();
		Thread t = new Thread(new MessageLoop());
		t.start();

		threadMessage("Waiting for MessageLoop thread to finish");
		// loop until MessageLoop
		// thread exits

		while (t.isAlive()) {
			threadMessage("Still waiting...");
			// Wait maximum of 1 second
			// for MessageLoop thread
			// to finish.
			t.join(1000);
			if (((System.currentTimeMillis() - startTime) > patience)
					&& t.isAlive()) {
				threadMessage("Tired of waiting!");
				t.interrupt();
				// Shouldn't be long now
				// -- wait indefinitely
				t.join();
			}
		}
		threadMessage("Finally!");
	}

}
